'use strict';

/**
 * Module dependencies.
 */
var mongoose = require('mongoose'),
    Schema = mongoose.Schema,
    crypto = require('crypto'),
    validator = require('validator'),
    baseController = require('../../../Base/server/controllers/BaseDoc.js');

/**
 * A Validation function for local strategy email
 */
var validateLocalStrategyEmail = function (email) {
    return (!this.updated || validator.isEmail(email));
};

var validateLocalStrategyPassword = function(password) {
    return (password && password.length >= 6);
};


var userModel = baseController.getBaseDocFields();
userModel.Code = {
    type: String,
    unique: '用户名已存在',
    required: '请输入用户名',
    trim: true
};
userModel.Name = {
    type: String,
    trim: true
};
userModel.Password = {
    type: String,
    default: '123456',
    validate: [validateLocalStrategyPassword, '密码至少6位']
};
userModel.UniqueID = {
    type: String,
    trim: true
};
userModel.Image = {
    type: String,
    default: 'users/img/default.png'
};
userModel.Email = {
    type: String,
    unique: true,
    trim: true,
    default: '',
    validate: [validateLocalStrategyEmail, '请输入一个合法的邮箱']
};
userModel.Salt = {
    type: String
};
userModel.Roles = {
    type: [{
        type: Schema.ObjectId,
        ref: 'Role'
    }]
};
userModel.Phone = {
    type: String,
    trim: true
};
userModel.Department = {
    type: Schema.ObjectId,
    ref: 'Department'
};
userModel.IsEffective = {
    type: Boolean
};
userModel.Remark = {
    type: String
};

/* For reset password */
userModel.ResetPasswordToken = {
    type: String
};
userModel.ResetPasswordExpires = {
    type: Date
};

var UserSchema = new Schema(userModel);
UserSchema.index({Name: 1});
UserSchema.index({Code: 1}, {"unique": true});

/**
 * Hook a pre save method to hash the password
 */
UserSchema.pre('save', function (next) {
    if (this.Password  && this.isModified('Password') || this.Password === '123456') {
        this.Salt = crypto.randomBytes(16).toString('base64');
        this.Password = this.hashPassword(this.Password);
    }
    if (this.Name === '') {
        this.Name = this.Code;
    }

    next();
});

/**
 * Create instance method for hashing a password
 */
UserSchema.methods.hashPassword = function (password) {
    if (this.Salt && password) {
        return crypto.pbkdf2Sync(password, new Buffer(this.Salt, 'base64'), 10000, 64).toString('base64');
    } else {
        return password;
    }
};

/**
 * Create instance method for authenticating user
 */
UserSchema.methods.authenticate = function (password, callback) {
    callback(this.Password === this.hashPassword(password));
};

/**
 * Find possible not used username
 */
UserSchema.statics.findUniqueUsername = function (username, suffix, callback) {
    var _this = this;
    var possibleUsername = username.toLowerCase() + (suffix || '');

    _this.findOne({
        Name: possibleUsername
    }, function (err, user) {
        if (!err) {
            if (!user) {
                callback(possibleUsername);
            } else {
                return _this.findUniqueUsername(username, (suffix || 0) + 1, callback);
            }
        } else {
            callback(null);
        }
    });
};

mongoose.model('User', UserSchema, 'User');
